package cn.mw.cmdb.processor;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.bean.copier.CopyOptions;
import cn.mw.cmdb.entity.InstanceInfoExtend;
import cn.mw.cmdb.param.InstanceSearchParam;
import cn.mw.cmdb.param.TableSearchParam;
import cn.mw.cmdb.service.impl.CmdbServiceManage;
import cn.mw.cmdb.service.impl.InstanceServiceImpl;
import cn.mw.cmdb.util.CMDBTool;
import cn.mw.cmdb.viewProcessor.RelateDataViewProcessor;
import cn.mw.cmdb.viewProcessor.ViewProcessorManage;
import cn.mw.microMonitorCommon.entity.cmdb.TableHeaderItem;
import com.google.common.base.Strings;

import java.util.*;
import java.util.stream.Collectors;

import static cn.mw.cmdb.entity.PropertyType.relationPath;
import static cn.mw.cmdb.processor.TreeProcessorBusiness.modelSystemPid;

/**
 * 业务系统Processor
 */
public class StaticsProcessorBusinessInstance implements TableDataProccessor {

    private CmdbServiceManage cmdbServiceManage;

    private TableSearchParam tableDataParam;

    private InstanceSearchParam instanceSearchParam;
    private TableDataProccessor tableDataProccessor;

    public StaticsProcessorBusinessInstance(CmdbServiceManage cmdbServiceManage, TableSearchParam tableDataParam,
                                            InstanceSearchParam instanceSearchParam, TableDataProccessor tableDataProccessor) {
        this.cmdbServiceManage = cmdbServiceManage;
        this.tableDataParam = tableDataParam;
        this.instanceSearchParam = instanceSearchParam;
        this.tableDataProccessor = tableDataProccessor;


    }

    @Override
    public List genData(TableDataProcessorContext context) throws Exception {
        InstanceServiceImpl instanceService = (InstanceServiceImpl) cmdbServiceManage.getModelService(InstanceServiceImpl.ID);
        List<InstanceInfoExtend> instanceInfos = new ArrayList<>();
        //忽略null值注入
        BeanUtil.copyProperties(tableDataParam, instanceSearchParam, CopyOptions.create().setIgnoreNullValue(true));
        //点击查询业务系统根节点,查询所有外部关联的数据
        if (Strings.isNullOrEmpty(tableDataParam.getId()) || modelSystemPid.equals(tableDataParam.getId())) {
            instanceSearchParam.exist(relationPath, true);
        } else {
            instanceSearchParam.setBussiness(tableDataParam.getId());
        }
        if(tableDataParam.isEnableMonitorStatus()){
            //查询资产状态
            instanceSearchParam.setEnableMonitorStatus(true);
        }
        //不分页查询,为了排序
        //instanceSearchParam.setPage(null);
        instanceInfos = instanceService.aggregateList(instanceSearchParam);
        List<Map> ret = new ArrayList<>();
        ViewProcessorManage processorManage = new ViewProcessorManage();

        List<TableHeaderItem> tableHeaderItems = context.getTableHeaderItems();
        if (null != instanceInfos && null != tableHeaderItems) {
            Set<RelateDataViewProcessor> relateDataViewProcess = processorManage.buildRelateDataViewProcessor(tableHeaderItems);
            Map<? extends Class<? extends RelateDataViewProcessor>, List<RelateDataViewProcessor>> collect = relateDataViewProcess.stream().collect(Collectors.groupingBy(s -> s.getClass()));
            Set<RelateDataViewProcessor> relateDataViewProcessors = new HashSet<>();
            collect.forEach((k,v)->{
                if(v!=null && v.size()>0){
                    RelateDataViewProcessor relateDataViewProcessor = v.get(0);
                    relateDataViewProcessors.add(relateDataViewProcessor);
                }
            });
            //初始化
            int seq = 0;
            for (InstanceInfoExtend instanceInfo : instanceInfos) {
                seq++;
                Map data = new LinkedHashMap();
                if (tableDataParam.isShowAllField()) {
                    Map<String, Object> dataMap = instanceInfo.getData();
                    data.putAll(dataMap);
                }
                for (TableHeaderItem item : tableHeaderItems) {
                    Object value = instanceInfo.getValue(item.getField());
                    data.put(item.getField(), value);
                }
                data.put(CMDBTool.getFieldName(InstanceInfoExtend::getModelName),instanceInfo.getModelName());
                data.put(CMDBTool.getFieldName(InstanceInfoExtend::getModelGroupName), instanceInfo.getModelGroupName());
                data.put(CMDBTool.getFieldName(InstanceInfoExtend::getModelId), instanceInfo.getModelId());
                data.put(CMDBTool.getFieldName(InstanceInfoExtend::getFinanceParentId), instanceInfo.getFinanceParentId());
                data.put(CMDBTool.getFieldName(InstanceInfoExtend::getGroupId), instanceInfo.getGroupId());ret.add(data);
//                data.put(SEQ, seq);

                if (null == relateDataViewProcessors || relateDataViewProcessors.size() == 0) {
                    continue;
                }
                for (RelateDataViewProcessor processor : relateDataViewProcessors) {
                    processor.init(instanceInfo, data);
                }
            }

            if (null == relateDataViewProcessors || relateDataViewProcessors.size() == 0) {
                return ret;
            }
            //查询外部服务关联数据
            for (RelateDataViewProcessor processor : relateDataViewProcessors) {
                processor.selectRelateData(context);
            }

            //设置关联数据
            for (Map s : ret) {
                for (RelateDataViewProcessor processor : relateDataViewProcessors) {
                    processor.setRelateData(s);
                }
            }
        }
        return ret;
    }

    @Override
    public List<TableHeaderItem> genDefaultTableHeader(Class clazz) throws Exception {
        List<TableHeaderItem> tableHeaderItems = tableDataProccessor.genDefaultTableHeader(clazz);
        return tableHeaderItems;
    }
}
